package com.hongxun.design.utils.serviceandclient;

import android.os.Handler;
import android.os.Message;

import com.alibaba.fastjson.JSON;
import com.hongxun.design.MyApp;
import com.hongxun.design.bean.ScanHotBean;
import com.hongxun.design.bean.service.ClientInfo;
import com.hongxun.design.bean.service.MessageData;
import com.hongxun.design.constant.Constant;
import com.hongxun.design.mytools.MString;
import com.hongxun.design.mytools.MyLog;
import com.hongxun.design.mytools.ToastShow;
import com.hongxun.design.object_properties.MyMessage;
import com.hongxun.design.utils.fastjson.FastJsonUtil;
import com.hongxun.design.utils.fileutil.FileSizeUtil;
import com.hongxun.design.utils.socketutil.LongWriterAndReader;
import com.hongxun.design.utils.socketutil.ReciveAndSend;

import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.ArrayList;
import java.util.List;

/**
 * Created by zerdoor_pc on 2016/7/24.
 */
public class ServiceUtil {
    private boolean isOnline = true;
    //    private List<String> ips=new ArrayList<>();
//    private List<SocketThread> threadList = new ArrayList<>();
    private List<ClientInfo> infoList;

    private MessageData messageData;
    Handler handler = new Handler() {
        @Override
        public void handleMessage(Message msg) {
            ToastShow.showShort(MyApp.activity, (String) msg.obj);
        }
    };
    Handler serviceUtilHandler;

    public ServiceUtil(Handler serviceUtilHandler) {
        this.serviceUtilHandler = serviceUtilHandler;
        infoList = new ArrayList<>();
        MyLog.L(MString.service + " setUpdate_client初始化" + infoList.size());
    }

    ServerSocket serverSocket;
    Thread serviceThread;

    public void setHandler(Handler handler) {
        this.serviceUtilHandler = handler;
    }

    public void start() {
        isOnline = true;
        serviceThread = new Thread(new Runnable() {
            @Override
            public void run() {
                try {
                    isOnline = false;
                    MyLog.L(MString.service + " setUpdate_初始化服务器！");
                    serverSocket = new ServerSocket(Constant.prot);
                    //serverSocket.bind(new InetSocketAddress("192.168.2.2",prot));
                    isOnline = true;
                    infoList.clear();
                    MyLog.L(MString.service + " setUpdate_清理数据！");
                } catch (IOException e) {
                    serviceUtilHandler.sendEmptyMessage(2);
                    MyLog.L(MString.service + " setUpdate_重新开启wifi！");
                    try {
                        serverSocket.close();
                    } catch (IOException e1) {
                        e1.printStackTrace();
                    }
                    serverSocket = null;
                    isOnline = false;
                    handler.sendMessage(MyMessage.getMessage(0, "服务器初始化失败！" + e));
                    MyLog.L(MString.service + " setUpdate_服务器初始化失败" + e);
                }

                try {

                    while (isOnline) {
                        MyLog.L(MString.service + " setUpdate_循环！");
                        Socket socket = serverSocket.accept();
                        String ip = getIP(socket);
                        boolean isfirst = true;
                        for (ClientInfo c : infoList) {
                            if (c.getIp().equals(ip)) {
                                infoList.remove(c);
                                break;
//                                isfirst = false;
//                                try {
//
//                                }catch (Exception e){}
//                                c.getThreadList().close();
//                                SocketThread socketThread = new SocketThread(socket, c);
//                                c.setSocket(socket);
//                                c.setThreadList(socketThread);
//                                socketThread.start();
//                                socketThread.writerHeart();
//                                MyLog.L(MString.service + " setUpdate_client更新" + c.getIp() + " ip=" + ip);
//                                break;
                            }
                        }
                        // if (isfirst) {
                        ClientInfo info = new ClientInfo();
                        info.setIp(ip);
                        SocketThread socketThread = new SocketThread(socket, info);
                        info.setSocket(socket);
                        info.setThreadList(socketThread);
                        infoList.add(info);
                        socketThread.start();
                        socketThread.writerHeart();
                        MyLog.L(MString.service + " setUpdate_client加入");
                        // }
                        // setUpdate();
                        MyLog.L(MString.service + " setUpdate_client" + infoList.size());
                        //handler.sendMessage(MyMessage.getMessage(0, "成功！"));
                        ServiceUtil.isSend=true;
                    }
                } catch (Exception e) {
                    MyLog.L(MString.service + " setUpdate_client异常" + e);

                }


            }
        });
        serviceThread.start();

    }


    private static String getIP(Socket client) {
        String s = String.valueOf(client.getRemoteSocketAddress());
        String[] tar = s.replaceAll("/", "").split(":");
        return tar[0];
    }

    /**
     * 发送给所有人*
     */
    private void sendToAllNotCheck() {
        if (infoList.size() > 0) {
            for (ClientInfo thread : infoList) {

                try {
                    thread.getThreadList().writer(1);
                } catch (IOException e) {
                    e.printStackTrace();
                }

            }

        }
        messageData = null;
    }

    private void sendToAll() {
        if (infoList.size() > 0) {
            for (ClientInfo thread : infoList) {
                if (thread.ischecked()) {
                    try {
                        thread.getThreadList().writer(1);
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            }

        }
        messageData = null;
    }

    private void sendToAll(long size) {
        if (infoList.size() > 0) {
            int i = 0;
            serviceUtilHandler.sendMessage(MyMessage.getMessage(1, i, 100 / infoList.size(), "" + infoList.size() * size));
            for (ClientInfo thread : infoList) {
                if (thread.ischecked()) {

                    try {
                        thread.getThreadList().writer(1);
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                    serviceUtilHandler.sendMessage(MyMessage.getMessage(1, i, 100 / infoList.size(), "" + infoList.size() * size));
                    i++;
                }
            }
            serviceUtilHandler.sendMessage(MyMessage.getMessage(1, -1, -1, "发送完成"));
        }
        messageData = null;
    }

    public int setInfoList(List<ClientInfo> infoList) {
        int i = 0;
        for (ClientInfo c : infoList) {
            for (ClientInfo c2 : this.infoList) {
                if (c.getUserName().equals(c2.getUserName()) && c.getIp().equals(c2.getIp())) {
                    c2.setIschecked(c.ischecked());
                    if (c.ischecked()) {
                        i++;
                    }
                    break;
                }
            }
        }
        return i;
    }

    public static  boolean isSend=true;
    public class SocketThread extends Thread {
        private Socket socket;
        private String temp;
        private boolean isopen = true;
        private boolean canSend = true;
        ClientInfo info;
        long startTime;
        boolean isrecive = true;

        public SocketThread(Socket socket, ClientInfo info) {
            this.socket = socket;
            this.info = info;
            startTime = System.currentTimeMillis();
        }

        public void run() {
            try {
                InputStream in = socket.getInputStream();
                OutputStream out = socket.getOutputStream();
                while (isopen) {
                    String s = LongWriterAndReader.reader(in, true, isrecive, serviceUtilHandler);//读取数据
                    if (s.length() > 0 && !s.equals("0") && !s.equals("-1")) {
                        ScanHotBean bean = FastJsonUtil.getScanHotBean(s);
                        MyLog.L(MString.service + "  接收消息s:" + s);
                        if (bean.getMessageType().equals(MString.userInfo)) {
                            info.setUserAvatar(bean.getUserAvatar());
                            info.setUserName(bean.getUserName());
                            info.setUserId(bean.getUserid());
                            ScanHotBean b = new ScanHotBean(MyApp.userInfo.getUsername(), MyApp.userInfo.getAvatar(), MString.userInfo);
                            b.setUserid(MyApp.userInfo.getUser_id());
                            sendMessageToAll(JSON.toJSONString(b));
//                            if (infoList.size() == 0) {
//                                infoList.add(info);
//                            }
                            setUpdate();
                            MyLog.L(MString.service + " setUpdate_message" + infoList.size());
                        } else if (bean.getMessageType().equals(MString.projectInfo)) {
                            serviceUtilHandler.sendEmptyMessage(3);//接收模式
                            isrecive = saveProjectList(bean.getMessage());//存储项目信息
                        }
                        startTime = System.currentTimeMillis();
                    } else if (s.equals("0")) {
                        MyLog.L(MString.service_heart + "  心跳");
                        startTime = System.currentTimeMillis();
                    } else if (s.equals("-1")) {
                        if (System.currentTimeMillis() - startTime > 20000) {
                            MyLog.L(MString.service + "  溢出");
                            try {
                                infoList.remove(info);
                            } catch (Exception e) {
                            }
                            isopen = false;
                            setUpdate();
                        }
                    }
                    Thread.sleep(3000);
                    if (isSend){

                        LongWriterAndReader.writer(out, 0, canSend);
                    }
//                    Thread.sleep(3000);
//                    LongWriterAndReader.writer(out, 0, canSend);
                }

            } catch (Exception e) {
                MyLog.L(MyApp.AppName + "server1:" + e.toString());
            } finally {
                if (socket != null) {
                    if (!socket.isClosed()) {
                        try {
                            socket.close();
                        } catch (IOException e) {
                            e.printStackTrace();
                        }
                    }
                }
            }

        }

        public void writer() throws IOException {
            if (messageData == null) return;
            LongWriterAndReader.writer(socket.getOutputStream(), messageData, canSend);
            messageData = null;
        }

        public void writer(int i) throws IOException {
            if (messageData == null) return;
//            if (messageData.getDataType() == 4) {
//                canSend = false;
//            }
            LongWriterAndReader.writer(socket.getOutputStream(), messageData, canSend);

        }

        public void writerHeart() {
            try {
                LongWriterAndReader.writer(socket.getOutputStream(), 0, canSend);
            } catch (IOException e) {
                e.printStackTrace();
            }
        }

        public Socket getSocket() {
            return socket;
        }

        public void setSocket(Socket socket) {
            this.socket = socket;
        }

        public void close() {
            isopen = false;
        }

    }


    public void sendMessageToAll(String s) {
        //handler.sendMessage(MyMessage.getMessage(0, "发送消息s:" + s));
        MyLog.L(MString.service + "  发送消息s:" + s);
        messageData = ReciveAndSend.getMessageData(1, s, "");
        sendToAllNotCheck();
    }

    public void sendMessage(String s) {
        // handler.sendMessage(MyMessage.getMessage(0, "发送消息s:" + s));
        MyLog.L(MString.service + "  发送消息s:" + s);
        messageData = ReciveAndSend.getMessageData(1, s, "");
        sendToAll();
    }

    public void sendMessage(String path, String fileName) {
        MyLog.L(MString.service + "  发送文件:path" + path);
        MyLog.L(MString.service + "  发送文件:fileName" + fileName);
        messageData = ReciveAndSend.getMessageData(4, path, fileName);
        try {
            sendToAll(FileSizeUtil.getFileSize(new File(path)));
        } catch (Exception e) {

        }
    }

    public void close() {
        try {
            for (ClientInfo i : infoList) {
                i.getThreadList().close();
            }
            infoList.clear();
        } catch (Exception e) {
        }
        try {
            isOnline = false;
            if (serverSocket != null) serverSocket.close();
            if (serviceThread != null) serviceThread.interrupt();
            serverSocket = null;
            serviceThread = null;
        } catch (IOException e) {
            e.printStackTrace();
        }

    }


    private boolean saveProjectList(String s) {
        return MyApp.File.saveProjectList(s);
    }

    /**
     * 通知UI更新*
     */
    public void setUpdate() {
        MyLog.L(MString.service + " setUpdate_数据刷新 " + infoList.size());
        serviceUtilHandler.sendEmptyMessage(0);
    }


    public List<ClientInfo> getInfoList() {
        MyLog.L(MString.service + " setUpdate_infoList.size()" + infoList.size());
        return infoList;
    }

}
